﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace TextMining
{
    public class Word   // Single word
    {
        public Document CurrentDocument { private set; get; }   // The document in which this word occured last time
        private int _currentOccurences = 0;   // Word's total occurences in the last document it occured
        private int _occuredDocuments = 0;   // The number of documents this word occured
        public bool IsImportant { set; get; }   // false: this word word has been removes as one of the
                                                // less important words

        private int _totalOccurences = 0;   // Word's total occurences in the whole data set
        private double _tfValue = 0;   // Word's current tf value

        public string Name { private set; get; }   // Word's name

        public Word(string name)
        {
            Name = name;   // add word's name
            IsImportant = true;
        }

        private double GetValue()   // Get word's current tf value
        {
            if (CurrentDocument == null)  // if this word hasn't occured yet
                return 0;   // then it has no current tf value
            return _tfValue + _currentOccurences / (double)CurrentDocument.WordCount;
            // Word's current tf value is its old tf value + its tf value in the last document
            // in which occured
        }

        public void AddOccurence(Document document)   // inform that this word has occured in a specific document
        {
            if (CurrentDocument == null)  // if it hasn't occured in any document yet
            {
                CurrentDocument = document;   // add this document as the last one occured
                _occuredDocuments++;   // one more document in which this word occured
            }
            else if (CurrentDocument.Id < document.Id)   // this word occured in a new document
            {
                _tfValue = GetValue();   // add its total tf value in its old tf value
                CurrentDocument = document;   // add this document as the last one occured
                _currentOccurences = 0;   // no occurences in the new document yet
                _occuredDocuments++;   // one more document in which this word occured
            }

            _currentOccurences++;   // one more occurence
            _totalOccurences++;   // one more occurence for this word in the data set
        }

        public double TfIdfValue(int totalDocuments)  // return the tf-idf() value
        {
            return GetValue() * Math.Log((totalDocuments + 1) / (double)_occuredDocuments);
        }

        public double TfIdfValue(int documentOccurences, int totalDocumentOccurences, int totalDocuments)
        {    // return the tf-idf for a single document
            return GetValue(documentOccurences, totalDocumentOccurences) * Math.Log((totalDocuments + 1) / (double)_occuredDocuments);
        }

        private double GetValue(int documentOccurences, int totalDocumentOccurences)
        {    // get word's tf value for a single document
            return documentOccurences / (double)totalDocumentOccurences;   
        }
    }
}
